/*
 *      Copyright (c) 2018-2028, Chill Zhuang All rights reserved.
 *
 *  Redistribution and use in source and binary forms, with or without
 *  modification, are permitted provided that the following conditions are met:
 *
 *  Redistributions of source code must retain the above copyright notice,
 *  this list of conditions and the following disclaimer.
 *  Redistributions in binary form must reproduce the above copyright
 *  notice, this list of conditions and the following disclaimer in the
 *  documentation and/or other materials provided with the distribution.
 *  Neither the name of the dreamlu.net developer nor the names of its
 *  contributors may be used to endorse or promote products derived from
 *  this software without specific prior written permission.
 *  Author: Chill 庄骞 (smallchill@163.com)
 */
package org.springblade.modules.admin.service.impl;

import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import lombok.AllArgsConstructor;
import org.springblade.core.log.exception.ServiceException;
import org.springblade.core.tool.utils.Func;
import org.springblade.modules.admin.dto.PartsPriceUpdateDTO;
import org.springblade.modules.admin.entity.PartsInfo;
import org.springblade.modules.admin.entity.PartsPrice;
import org.springblade.modules.admin.service.IPartsInfoService;
import org.springblade.modules.admin.vo.PartsInfoVO;
import org.springblade.modules.admin.vo.PartsPriceVO;
import org.springblade.modules.admin.mapper.PartsPriceMapper;
import org.springblade.modules.admin.service.IPartsPriceService;
import org.springblade.core.mp.base.BaseServiceImpl;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.annotation.Lazy;
import org.springframework.stereotype.Service;
import com.baomidou.mybatisplus.core.metadata.IPage;
import org.springframework.transaction.annotation.Transactional;

import java.util.ArrayList;
import java.util.List;
import java.util.stream.Collectors;

/**
 * 配件销售价格表 服务实现类
 *
 * @author ysq
 * @since 2023-08-09
 */
@Service
public class PartsPriceServiceImpl extends BaseServiceImpl<PartsPriceMapper, PartsPrice> implements IPartsPriceService {

	@Lazy
	@Autowired
	private IPartsInfoService partsInfoService;

	@Override
	public IPage<PartsInfoVO> selectPartsPricePage(IPage<PartsInfoVO> page, PartsInfoVO partsInfo) {
		return page.setRecords(baseMapper.selectPartsPricePage(page, partsInfo));
	}

	@Override
	public PartsInfoVO detail(Long partId) {
		PartsInfoVO partsInfo = new PartsInfoVO();
		partsInfo.setId(partId);
		List<PartsInfoVO> list = baseMapper.selectPartsPricePage(null, partsInfo);
		return list.isEmpty() ? null : list.get(0);
	}

	@Transactional(rollbackFor = Exception.class)
	@Override
	public boolean submitPartsPrice(PartsPriceUpdateDTO param) {
		PartsInfo partsInfo = partsInfoService.getById(param.getPartsId());
		if (Func.isEmpty(partsInfo)) {
			throw new ServiceException("配件信息数据异常！");
		}
		if (!Func.equalsSafe(partsInfo.getCostPrice(), param.getCostPrice())) {
			// 更新成本单价
			partsInfo.setCostPrice(param.getCostPrice());
			partsInfoService.updateById(partsInfo);
		}

		// 更新、新增、删除销售价格
		List<PartsPrice> saveOrUpdateList = new ArrayList<>(4);
		List<PartsPrice> deleteList = new ArrayList<>(4);
		List<PartsPrice> oldPartsPrices = this.list(Wrappers.<PartsPrice>lambdaQuery().eq(PartsPrice :: getPartsId, param.getPartsId()));
		List<PartsPrice> newPartsPrices = param.getPartsPrices();
		long leaveIdCount = newPartsPrices.stream().map(t -> t.getPriceLeaveId()).distinct().count();
		if (newPartsPrices.stream().count() != leaveIdCount) {
			throw new ServiceException("保存失败，同类型【价格等级】无法重复添加");
		}

		if (oldPartsPrices.isEmpty() && newPartsPrices.isEmpty()) {
			return true;
		}

		if (oldPartsPrices.isEmpty() || newPartsPrices.isEmpty()) {
			if (oldPartsPrices.isEmpty()) {
				saveOrUpdateList.addAll(newPartsPrices);
			} else {
				deleteList.addAll(oldPartsPrices);
			}
		} else {
			// 处理需要删除的老数据
			List<Long> newIds = newPartsPrices.stream().filter(t -> t.getId() != null).map(t -> t.getId()).collect(Collectors.toList());
			List<PartsPrice> needDelData = oldPartsPrices.stream().filter(t -> !newIds.contains(t.getId())).collect(Collectors.toList());
			deleteList.addAll(needDelData);
			saveOrUpdateList.addAll(newPartsPrices);
		}

		if (saveOrUpdateList.size() > 0) {
			this.saveOrUpdateBatch(saveOrUpdateList);
		}

		if (deleteList.size() > 0) {
			this.deleteLogic(deleteList.stream().map(t -> t.getId()).collect(Collectors.toList()));
		}

		return true;
	}

	@Override
	public boolean removePartsPrices(Long partsId) {
		PartsInfo partsInfo = partsInfoService.getById(partsId);
		if (Func.isEmpty(partsInfo)) {
			throw new ServiceException("配件信息数据异常！");
		}

		List<PartsPrice> partsPrices = this.list(Wrappers.<PartsPrice>lambdaQuery().eq(PartsPrice :: getPartsId, partsId));
		if (Func.isNotEmpty(partsPrices)) {
			List<Long> delIds = partsPrices.stream().map(t -> t.getId()).collect(Collectors.toList());
			return this.deleteLogic(delIds);
		}

		return false;
	}
}
